// controllers/depositController.js
const Deposit = require("../models/depositModel");
const Account = require("../models/accountModel");
const User = require("../models/userModel");

// CREATE Deposit
exports.createDeposit = async (req, res) => {
  try {
    const { depositDate, referenceNo, debitAccount, creditAccount, amount, note } = req.body;
    
    if (!depositDate || !debitAccount || !creditAccount || !amount) {
      return res.status(400).json({ success: false, message: "Missing required fields" });
    }
    
    // Set createdBy from req.body or from req.user if available
    let createdBy = req.body.createdBy || null;
    if (req.user && req.user.id) {
      createdBy = req.user.id;
    }
    
    // Prevent same account for debit and credit
    if (debitAccount === creditAccount) {
      return res.status(400).json({ success: false, message: "Debit and credit accounts cannot be the same" });
    }
    
    // Validate debit account
    const debitAccDoc = await Account.findById(debitAccount);
    if (!debitAccDoc) {
      return res.status(400).json({ success: false, message: "Invalid debit account" });
    }
    
    // Validate credit account
    const creditAccDoc = await Account.findById(creditAccount);
    if (!creditAccDoc) {
      return res.status(400).json({ success: false, message: "Invalid credit account" });
    }
    
    // Create new Deposit document
    const newDeposit = new Deposit({
      depositDate,
      referenceNo,
      debitAccount,
      creditAccount,
      amount,
      note,
      createdBy,
    });
    
    // If authenticated user is available, set createdByModel accordingly
    if (req.user && req.user.id) {
      newDeposit.createdBy = req.user.id;
      newDeposit.createdByModel = req.user.role.toLowerCase() === "admin" ? "Admin" : "User";
    }
    
    const savedDeposit = await newDeposit.save();
    return res.status(201).json({ success: true, message: "Deposit created", data: savedDeposit });
  } catch (error) {
    console.error("Error creating deposit:", error);
    return res.status(500).json({ success: false, message: error.message });
  }
};

// GET All Deposits (with computed creatorName)
exports.getAllDeposits = async (req, res) => {
  try {
    const deposits = await Deposit.find()
      .populate("debitAccount", "accountName accountNumber")
      .populate("creditAccount", "accountName accountNumber")
      .populate("createdBy", "FirstName LastName name");
      
    // Process deposits to compute creatorName
    const processedDeposits = deposits.map((deposit) => {
      let creatorName = "";
      if (deposit.createdBy) {
        if (deposit.createdBy.name) {
          creatorName = deposit.createdBy.name;
        } else if (deposit.createdBy.FirstName && deposit.createdBy.LastName) {
          creatorName = `${deposit.createdBy.FirstName} ${deposit.createdBy.LastName}`;
        }
      }
      return { ...deposit.toObject(), creatorName };
    });

    return res.status(200).json({ success: true, data: processedDeposits });
  } catch (error) {
    console.error("Error fetching deposits:", error);
    return res.status(500).json({ success: false, message: error.message });
  }
};

// GET Single Deposit (with computed creatorName)
exports.getDepositById = async (req, res) => {
  try {
    const deposit = await Deposit.findById(req.params.id)
      .populate("debitAccount", "accountName accountNumber")
      .populate("creditAccount", "accountName accountNumber")
      .populate("createdBy", "FirstName LastName name");
      
    if (!deposit) {
      return res.status(404).json({ success: false, message: "Deposit not found" });
    }
    
    let creatorName = "";
    if (deposit.createdBy) {
      if (deposit.createdBy.name) {
        creatorName = deposit.createdBy.name;
      } else if (deposit.createdBy.FirstName && deposit.createdBy.LastName) {
        creatorName = `${deposit.createdBy.FirstName} ${deposit.createdBy.LastName}`;
      }
    }
    
    return res.status(200).json({ success: true, data: { ...deposit.toObject(), creatorName } });
  } catch (error) {
    console.error("Error fetching deposit:", error);
    return res.status(500).json({ success: false, message: error.message });
  }
};

// UPDATE Deposit
exports.updateDeposit = async (req, res) => {
  try {
    const { id } = req.params;
    const { depositDate, referenceNo, debitAccount, creditAccount, amount, note } = req.body;

    const updated = await Deposit.findByIdAndUpdate(
      id,
      { depositDate, referenceNo, debitAccount, creditAccount, amount, note },
      { new: true }
    );

    if (!updated) {
      return res.status(404).json({ success: false, message: "Deposit not found" });
    }
    return res.status(200).json({ success: true, message: "Deposit updated", data: updated });
  } catch (error) {
    console.error("Error updating deposit:", error);
    return res.status(500).json({ success: false, message: error.message });
  }
};

// DELETE Deposit
exports.deleteDeposit = async (req, res) => {
  try {
    const deleted = await Deposit.findByIdAndDelete(req.params.id);
    if (!deleted) {
      return res.status(404).json({ success: false, message: "Deposit not found" });
    }
    return res.status(200).json({ success: true, message: "Deposit deleted" });
  } catch (error) {
    console.error("Error deleting deposit:", error);
    return res.status(500).json({ success: false, message: error.message });
  }
};
